#!/usr/bin/env python

import os,commands

class Reminder:

    def __init__(self):
        """there will be documentation here, soon
        """

        self.database=os.environ["HOME"]+'/.renoter'
        if not os.path.exists(self.database):
            print '\n Database does not exist. \n Will create a new one "%s", could take a few seconds. \n' % self.database
            open(self.database, 'w').close()
            self.update_db()
        else:
            self.read_db()

    def update_db(self):
        """update database with all reminders and notes existing around the
        perimeters of the system"""

        cmd='updatedb -l 0 -o $HOME/.renoterdb -U $HOME/'
        os.system(cmd)

        cmd="locate -d $HOME/.renoterdb '*.note'"
        self.notes = commands.getoutput(cmd).split('\n')
        cmd="locate -d $HOME/.renoterdb '*.reminder'"
        self.reminders = commands.getoutput(cmd).split('\n')

        f=open(self.database,'w')
        for note in self.notes:
            f.write(note+'\n')
        for reminder in self.reminders:
            f.write(reminder+'\n')
        f.close()

        return self

    def read_db(self):
        """read in database file without updating it before"""

        self.notes = []
        self.reminders = []
        f = open(self.database)
        lines = f.readlines()
        for line in range(len(lines)):
            try:
                lines[line].index('.note')
            except ValueError:
                try:
                    lines[line].index('.reminder')
                except ValueError:
                    print lines[line]+' does not match requested format'
                else:
                    self.reminders.append(lines[line].replace('\n',''))
                continue
            else:
                self.notes.append(lines[line].replace('\n',''))

    def show_note(self,n):
        """function to display the content of a single note"""
        
        f = open(self.notes[n],'r')
        lines = f.readlines()
        print '\n '+ self.notes[n].split('/')[-1].replace('.note','')+':'
        print ' '+(len(self.notes[n].split('/')[-1].replace('.note',''))+1)*'-'+'\n'
        for line in range(len(lines)):
            print '    '+lines[line].replace('\n','')
        print '\n'

    def show_reminder(self,n):
        """function to display the content of a single reminder"""
        
        f = open(self.reminders[n],'r')
        lines = f.readlines()
        print '\n '+ self.reminders[n].split('/')[-1].replace('.reminder','')+':'
        print ' '+(len(self.reminders[n].split('/')[-1].replace('.reminder',''))+1)*'-'+'\n'
        for line in range(len(lines)):
            print '    '+lines[line].replace('\n','')
        print '\n'

    def list_notes(self):
        """function to display notes in a short and convenient fashion"""
        
        notes = []
        maxl = 0
        for n in range(len(self.notes)):
            notes.append(self.notes[n].split('/')[-1].replace('.note',''))
            if len(notes[-1]) >maxl:
                maxl = len(notes[-1])

        spacer = '  '
        numb = len(str(len(notes)-1)) + len(spacer)
        leng=40
        empt=' '
        print ' _______________________________________\n ________________NOTES__________________ \n'
        for n in range(len(notes)):
            if len(notes[n]) > leng-numb-len(spacer):
                print (numb-len(str(n)))*empt+str(n)+spacer+(leng-len(notes[n])-numb)*empt+notes[n][:leng-numb-2]
            else:
                print (numb-len(str(n)))*empt+str(n)+(leng-len(notes[n])-numb)*empt+notes[n] #+(maxl-len(notes[n]))*empt #flush right

#other print statements:
#print (numb-len(str(n)))*empt+str(n)+(leng-len(notes[n])-numb-(maxl-len(notes[n]))/2)*empt+notes[n] #+(maxl-len(notes[n]))*empt #concentric
#print (numb-len(str(n)))*empt+str(n)+(leng-len(notes[n])-numb-(maxl-len(notes[n])))*empt+notes[n] #+(maxl-len(notes[n]))*empt #flush left
        print '\n'

    def list_reminders(self):

        reminders = []
        maxl = 0
        for r in range(len(self.reminders)):
            reminders.append(self.reminders[r].split('/')[-1].replace('.reminder',''))
            if len(reminders[-1]) >maxl:
                maxl = len(reminders[-1])

        spacer = '  '
        numb = len(str(len(reminders)-1)) + len(spacer)
        leng=40
        empt=' '
        print ' _______________________________________\n ______________REMINDERS________________\n'
        for r in range(len(self.reminders)):
            if len(reminders[r]) > leng-numb-len(spacer):
                print (numb-len(str(r)))*empt+str(r)+spacer+(leng-len(reminders[r])-numb)*empt+reminders[r][:leng-numb-2]
            else:
                print (numb-len(str(r)))*empt+str(r)+(leng-len(reminders[r])-numb)*empt+reminders[r]
        print '\n'

    def edit_note(self,n):
        """edit given note n within editor given in system variable $EDITOR"""

        os.system('$EDITOR'+' '+self.notes[n])

    def edit_reminder(self,n):
        """edit given note n within editor given in system variable $EDITOR"""

        os.system('$EDITOR'+' '+self.reminders[n])

    def remove_note(self,n):
        """remove note from database"""

        for cmd in ['rm $HOME/.renoter','rm %s' %self.notes[n]]:
            os.system(cmd)

        self.notes.remove(self.notes[n])

        f=open(self.database,'w')
        for note in self.notes:
            f.write(note+'\n')
        for reminder in self.reminders:
            f.write(reminder+'\n')
        f.close()

        return self

    def remove_reminder(self,n):
        """remove reminder from database"""

        for cmd in ['rm $HOME/.renoter','rm %s' %self.reminders[n]]:
            os.system(cmd)

        self.reminders.remove(self.reminders[n])

        f=open(self.database,'w')
        for note in self.notes:
            f.write(note+'\n')
        for reminder in self.reminders:
            f.write(reminder+'\n')
        f.close()

        return self

def main():
    """program entry point, if run directly"""

    from optparse import OptionParser
    import sys
    import os

    # construct the option parser
    parser = OptionParser(usage='%prog [options]')

    parser.add_option('-s', '--show',
	              dest='show', action='store_true', help='show current reminders and notes')

    parser.add_option('-u', '--update',
	              dest='update', action='store_true', help='update the database of reminders and notes')

    parser.add_option('-n', '--notes',
	              dest='notes', action='store_true', help='activate notes only')

    parser.add_option('-r', '--reminders',
	              dest='reminders', action='store_true', help='activate reminders only')

    parser.add_option('-e', '--edit',
	              dest='edit', action='store', type='int',
                  nargs=1,
		          help='note or reminder to edit')

    parser.add_option('-c', '--content',
	              dest='content', action='store', type='int',
                  nargs=1,
		          help='show content of note or reminder')

    parser.add_option('-d', '--delete',
	              dest='delete', action='store', type='int',
                  nargs=1,
		          help='delete note or reminder')

    parser.add_option('-l', '--location',
	              dest='location', action='store', type='int',
                  nargs=1,
		          help='show location of note or reminder')

    # run the option parser and get results
    (options, args) = parser.parse_args()

    # if filename not given, use stdout for output

    if len(sys.argv) == 1:
        options.show,options.notes = True, True
    elif len(sys.argv) == 2:
        try:
            options.content = int(sys.argv[1])
        except ValueError:
            content = False

    if (options.edit is not None or options.show is not None or options.content is not None or options.delete is not None or options.location is not None) and not (options.notes or options.reminders):
        options.notes = True

    if options.reminders and not (not options.show and (options.edit is not None or options.content is not None or options.delete is not None or options.location is not None)):
        options.show = True

    r = Reminder()

    if options.update:
        r.update_db()

    if options.show and options.notes:
        r.list_notes()
    elif options.show and options.reminders:
        r.list_reminders()
    elif options.show and not options.reminders and not options.notes:
        r.list_notes()
        r.list_reminders()

    if options.edit is not None:
        if options.notes:
            try:
                r.edit_note(options.edit)
            except:
                print '\n Note is not existent!!!\n'
        elif options.reminders:
            try:
                r.edit_reminder(options.edit)
            except:
                print '\n Reminder is not existent!!!\n'
        else:
            print '\n You have to tell me if you want to edit a note or a reminder!!!\n'

    if options.content is not None:
        if options.notes:
            try:
                r.show_note(options.content)
            except:
                print '\n Note is not existent!!!\n'
        elif options.reminders:
            try:
                r.show_reminder(options.content)
            except:
                print '\n Reminder is not existent!!!\n'
        else:
            print '\n You have to tell me if you want to show a note or a reminder!!!\n'

    if options.delete is not None:
        if options.notes:
            try:
                r.remove_note(options.delete)
            except:
                print '\n Note is not existent!!!\n'
        elif options.reminders:
            try:
                r.remove_reminder(options.delete)
            except:
                print '\n Reminder is not existent!!!\n'
        else:
            print '\n You have to tell me if you want to delete a note or a reminder!!!\n'

    if options.location is not None:
        if options.notes:
            try:
                print '\n ' + r.notes[options.location].replace('/'+r.notes[options.location].split('/')[-1],'') + '\n'
            except:
                print '\n Note is not existent!!!\n'
        elif options.reminders:
            try:
                print '\n ' + r.reminders[options.location].replace('/'+r.reminders[options.location].split('/')[-1],'') + '\n'
            except:
                print '\n Note is not existent!!!\n'
        else:
            print '\n You have to tell me if you want to delete a note or a reminder!!!\n'


if __name__ == '__main__':
    main()
